package com.tanhua.server.service;

import com.alibaba.fastjson.JSON;
import com.tanhua.autoconfig.template.FaceTemplate;
import com.tanhua.autoconfig.template.OssTemplate;
import com.tanhua.commons.constant.Constants;
import com.tanhua.commons.exception.TanHuaException;
import com.tanhua.dubbo.api.db.UserInfoApi;
import com.tanhua.model.db.User;
import com.tanhua.model.db.UserInfo;
import com.tanhua.model.vo.ErrorResult;
import com.tanhua.model.vo.UserInfoVo;
import com.tanhua.server.interceptor.UserHolder;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.config.annotation.DubboReference;
import org.joda.time.DateTime;
import org.joda.time.Years;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;

@Service
@Slf4j
public class UserInfoService {

    @Autowired
    private StringRedisTemplate stringRedisTemplate;

    @Autowired
    private FaceTemplate faceTemplate;

    @Autowired
    private OssTemplate ossTemplate;

    @DubboReference
    private UserInfoApi userInfoApi;

    /**
     * 用户注册-保存信息
     * @param userInfoVo
     */
    public void save(UserInfoVo userInfoVo) {
        //1. vo 转 pojo UserInfo
        UserInfo userInfo = new UserInfo();
        //User loginUser = getUserByToken(token);
        // 复制对象的属性值，条件：属性名要相同且属性的类型必须一致
        // p1: 复制到来源， p2: 复制到的目标对象。 把p1的属性值复制给p2
        BeanUtils.copyProperties(userInfoVo, userInfo);
        // copy属性值时会把id设置为null, 所以要在复制完属性后再来设置id
        userInfo.setId(UserHolder.getUserId());
        //1.1 通过出生年月日获取年龄
        int age = getAgeByBirthday(userInfo.getBirthday());
        userInfo.setAge(age);
        //2. 调用api保存用户信息
        userInfoApi.add(userInfo);
    }

    /**
     * 通过出生年月日，获取年龄
     * @param birthday  yyyy-MM-dd
     * @return
     */
    private int getAgeByBirthday(String birthday) {
        // p1: 出生年月日
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        Date birthdayDate = null;
        try {
            birthdayDate = sdf.parse(birthday);
        } catch (ParseException e) {
            log.error("获取用户年龄失败!", e);
            return 0;
        }
        // p2: 当前系统时间
        Years years = Years.yearsBetween(new DateTime(birthdayDate), DateTime.now());
        return years.getYears();
    }


    /**
     * 用户注册- 上传头像
     * @param headPhoto
     */
    public void uploadAvatar(MultipartFile headPhoto) {
        //0 获取登录用户id
        Long loginUserId = UserHolder.getUserId();
        //1. 检测人脸
        try {
            if (faceTemplate.detect(headPhoto.getBytes())) {
                //3. 上传阿里Oss  headPhoto.getName()=参数名headPhoto  getOriginalFilename文件名
                String avatar = ossTemplate.upload(headPhoto.getOriginalFilename(), headPhoto.getInputStream());
                //4. 更新用户的头像
                //4.1 创建pojo, 设置头像地址
                UserInfo pojo = new UserInfo();
                //4.2 设置登录用户id, 更新时用它做为条件
                pojo.setId(loginUserId);
                pojo.setAvatar(avatar);
                //5. 调用api更新
                userInfoApi.update(pojo);
            }else{
                throw new TanHuaException(ErrorResult.faceError());
            }
        } catch (IOException e) {
            throw new TanHuaException("上传头像失败");
        }

    }

    /**
     * 获取用户信息
     * @param userID
     * @param huanxinID
     * @return
     */
    public UserInfoVo getUserInfo(Long userID, Long huanxinID) {
        //1. 默认使用登录用户id
        Long searchUserId = UserHolder.getUserId();
        if(null != userID){
            searchUserId = userID;
        }
        if (null != huanxinID){
            searchUserId = huanxinID;
        }
        //2. 调用api查询用户详情
        UserInfo pojo = userInfoApi.findById(searchUserId);
        //3. 把pojo转成vo
        UserInfoVo vo = new UserInfoVo();
        BeanUtils.copyProperties(pojo, vo);
        //3.1 年龄转成字符串
        vo.setAge(pojo.getAge().toString());
        //4. 返回
        return vo;
    }

    /**
     * 用户资料 更新
     * @param vo
     */
    public void updateUserInfo(UserInfoVo vo) {
        //1. 获取登录用户id
        Long loginUserId = UserHolder.getUserId();
        //2. vo转pojo
        UserInfo pojo = new UserInfo();
        BeanUtils.copyProperties(vo, pojo);
        //3. 计算年龄
        pojo.setAge(getAgeByBirthday(vo.getBirthday()));
        pojo.setId(loginUserId);
        //4. 调用api更新
        userInfoApi.update(pojo);
    }

    /**
     * 记录用户查看 访客列表的时间
     * @param type
     */
    public void recordDate(int type) {
        if(type == 4){
            String redisKey = Constants.VISITORS_USER;
            String whoKey = UserHolder.getUserId().toString();
            stringRedisTemplate.opsForHash().put(redisKey, whoKey,System.currentTimeMillis() + "");
        }
    }
}
